#define GROUP_WIDTH  (1000)
#define GROUP_HEIGHT (1)
#define GROUP_DEPTH  (1)

#define ENTITY_TO_FOLLOW_OFFSET (5)
#define FOLLOW_SPEED (0.25f)

cbuffer cbImmutable : register (b0) {
	uint gDispatchGroupsY;
};

RWStructuredBuffer<float4> gEntitiesCenterPosW : register(u0);

[numthreads(GROUP_WIDTH, GROUP_HEIGHT, GROUP_DEPTH)]
void 
main(in const uint3 dispatchThreadId : SV_DispatchThreadID) {
	// We do not use Z coordinate in num threads or dispatch thread.
	// Then index will be iIndex * J + jIndex
	const uint index = dispatchThreadId.x * gDispatchGroupsY + dispatchThreadId.y;

	// Update current entity center position based on:
	// Another particle that we choose based on an offset
	// A velocity that is unit vector from current particle
	// to target particle multiplied by a constant.
	const uint nextIndex = index + ENTITY_TO_FOLLOW_OFFSET;
	const float4 oldCenterPosW = gEntitiesCenterPosW[index];
	const float4 nextCenterPosW = gEntitiesCenterPosW[nextIndex];
	const float4 velW = mul(normalize(nextCenterPosW - oldCenterPosW), FOLLOW_SPEED);
	const float4 newCenterPosW = oldCenterPosW + velW;
	gEntitiesCenterPosW[index] = newCenterPosW;
}